package com.example.teamwork.Shrio.Realm;

import com.example.teamwork.Shrio.Bean.ActiveUser;
import com.example.teamwork.Shrio.Token.JWTToken;
import com.example.teamwork.Shrio.Util.JWTUtil;
import com.example.teamwork.pojo.Permission;
import com.example.teamwork.pojo.Role;
import com.example.teamwork.pojo.User;
import com.example.teamwork.service.UserService;
import org.apache.commons.collections.CollectionUtils;
import org.apache.commons.lang3.StringUtils;
import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger;
import org.apache.shiro.SecurityUtils;
import org.apache.shiro.authc.*;
import org.apache.shiro.authz.AuthorizationInfo;
import org.apache.shiro.authz.SimpleAuthorizationInfo;
import org.apache.shiro.realm.AuthorizingRealm;
import org.apache.shiro.subject.PrincipalCollection;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.util.HashSet;
import java.util.List;
import java.util.Set;

/**
 * 〈一句话功能简述〉<br> 
 * 〈〉
 * @author  SongPeng
 * @date  2021/10/19 14:30
 * @version 1.0
 */

@Service
public class MyRealm extends AuthorizingRealm {

    private static final Logger LOGGER = LogManager.getLogger(MyRealm.class);
    @Autowired
    private UserService userService;

    /**
     * 大坑！，必须重写此方法，不然Shiro会报错
     */
    @Override
    public boolean supports(AuthenticationToken token) {
        return token instanceof JWTToken;
    }

    /**
     * 只有当需要检测用户权限的时候才会调用此方法，例如checkRole,checkPermission之类的
     */
    @Override
    protected AuthorizationInfo doGetAuthorizationInfo(PrincipalCollection principals) {
        System.out.println("--------------------");
        System.out.println("执行权限验证");
        ActiveUser activeUser = (ActiveUser) SecurityUtils.getSubject().getPrincipal();
        User user = activeUser.getUser();
        SimpleAuthorizationInfo simpleAuthorizationInfo = new SimpleAuthorizationInfo();
        List<Role> Roles = userService.getRolesByUserId(user.getUserId());
        HashSet rolesets=new HashSet();
        List<Permission> percussionist;
        for(Role role: Roles){
            rolesets.add(role.getRoleName());
        }
        Set<String> perms=new HashSet();
            percussionist=userService.findPermissionsByRoles(Roles);
            for(Permission permission:percussionist) {
                perms.add(permission.getOperateName());
            }
        simpleAuthorizationInfo.addRoles(rolesets);
        simpleAuthorizationInfo.addStringPermissions(perms);
        return simpleAuthorizationInfo;
    }
//    new HashSet<>(Arrays.asList(user_info.getPermission().split(","))
//    //到数据库查询当前登录用户的授权字符串
//    //获取当前登录用户
//    Subject subject = SecurityUtils.getSubject();
//    String username = (String) subject.getPrincipal();
//    User_info user_info=adUserService.findByName(username);
//    List<Role> Roles = roleService.getRolesByUserId(user_info.getId());
//    List<Permission> percussionist;
//    Set<String> perms=new HashSet<>();
//        for (Role role : Roles) {
//        percussionist=permissionService.findPermissionsByRole(role.getId());
//        for(Permission permission:percussionist){
//            perms.add(permission.getPermission());
//        }
//    }
    /**
     * 默认使用此方法进行用户名正确与否验证，错误抛出异常。
     */
    @Override
    protected AuthenticationInfo doGetAuthenticationInfo(AuthenticationToken auth) throws AuthenticationException {
        System.out.println("---------------------------");
        System.out.println("执行认证逻辑");
        String token = (String) auth.getCredentials();
        // 解密获得name，用于和数据库进行对比
        String name = JWTUtil.getUsername(token);
        if (name == null) {
            throw new AuthenticationException("token错误，请重新登录");
        }
        User user = userService.getUserByname(name);
        if (user == null) {
            throw new AccountException("用户不存在");
        }
        if(user.getUserStatus()==0){
            throw new LockedAccountException("账号已被锁定!");
        }
        if(JWTUtil.isExpire(token)){
            throw new AuthenticationException(" token过期，请重新登入！");
        }
        if (! JWTUtil.verify(token, name, user.getPassword())) {
            throw new CredentialsException("密码错误!");
        }
        //如果验证通过，获取用户的角色
        List<Role> roles= userService.getRolesByUserId(user.getUserId());
        //查询用户的所有菜单(包括了菜单和按钮)
        List<Permission> permissions=userService.findPermissionsByRoles(roles);
        Set<String> urls=new HashSet<>();
        Set<String> perms=new HashSet<>();
        if(!CollectionUtils.isEmpty(permissions)){
            for (Permission permission : permissions) {
                String url = permission.getPermissionUrl();
                String per = permission.getOperateName();
                if(!StringUtils.isEmpty(url)){
                    urls.add(permission.getPermissionUrl());
                }
                if(permission.getPermissionType()==1&&!StringUtils.isEmpty(per)){
                    perms.add(permission.getOperateName());
                }
            }
        }
        //过滤出url,和用户的权限
        ActiveUser activeUser = new ActiveUser();
        activeUser.setRoles(roles);
        activeUser.setUser(user);
        activeUser.setPermissionList(permissions);
        activeUser.setUrls(urls);
        activeUser.setPermissions(perms);
        return new SimpleAuthenticationInfo(activeUser, token, getName());
    }
}

 
